package MyArrayList.impl;

import MyArrayList.myException.MyArrayListException;
import MyArrayList.myInterface.MyList;

import java.util.Arrays;

public class MyArrayList implements MyList {


    private Object[] elementData;

    private int size;

    private Object[] DEFAULT_EMPTY_ELEMENTDATA={};

    private int DEFAULT_MAX_CAPACITY=Integer.MAX_VALUE-8;

    //构造器
    public MyArrayList(){
        elementData=DEFAULT_EMPTY_ELEMENTDATA;
    }

    public MyArrayList(int length){
        elementData=DEFAULT_EMPTY_ELEMENTDATA;
    }

    /**
     * 数组扩容:
     *
     */
    private void grow(int minCapacity){
        //现在的数组的长度
        int oldCapacity=elementData.length;
        //新数组的长度，在现有数组长度的基础上，在增加1/2。这样不至于增加太多，也不至于太少，导致增加次数过多
        int newCapacity=oldCapacity+(oldCapacity>>1);
        //如果新的数组的长度>目前需要的数组长度，则扩大现在需要的数组长度
        if(minCapacity>newCapacity){
            newCapacity=minCapacity;
        }
        //如果新的数组长度大于设定的最大值，则直接去Integer能表示的最大值
        if (newCapacity>DEFAULT_MAX_CAPACITY){
            newCapacity=Integer.MAX_VALUE;
        }
        //通过数组拷贝，将原数组进行扩容。 深拷贝和浅拷贝
        elementData= Arrays.copyOf(elementData,newCapacity);
    }

    public int size() {
        //返回的是元素的个数，而不是数组的长度，所以只有往List中添加了元素之后，size才会增加

        return size;
    }

    public Object get(int index) {
        if(index<0 || index>=size) {
            throw new ArrayIndexOutOfBoundsException("ArrayIndexOutOfBoundsException current:index"+index+",size:"+size);
        }
        return elementData[index];
    }

    public boolean isEmpty() {
        return size==0;
    }

    public boolean contains(Object element) {
        for (Object obj:elementData) {
            if(element==obj){
                return true;
            }
        }
        return false;
    }

    public void add(Object element) {
        if (size>=elementData.length) {
            grow(size+1);
        }
        elementData[size++] = element;
    }

    public void remove(Object element) {
        int i = indexOf(element);
        if (i==-1) {
            throw new MyArrayListException("没有此删除的元素");
        }
        remove(i);
    }

    public void remove(int index) {
        if (index<0 || index>=size) {
            throw new ArrayIndexOutOfBoundsException("ArrayIndexOutOfBoundsException current:index"+index+",size:"+size);
        }
        //用一个新数组去装
        Object[] newArray = new Object[size - 1];
        System.arraycopy(elementData,0,newArray,0,index);
        System.arraycopy(elementData,index+1,newArray,index,size-index-1);
        elementData = newArray;
        size--;
    }

    public void add(int index, Object element) {
        if (index<0 || index>=size) {
            throw new ArrayIndexOutOfBoundsException("ArrayIndexOutOfBoundsException current:index"+index+",size:"+size);
        }
        //用一个新数组去装
        Object[] newArray = new Object[size + 1];
        System.arraycopy(elementData,0,newArray,0,index);
        newArray[index] = element;
        System.arraycopy(elementData,index+1,newArray,index+1,size-index);
        elementData = newArray;
        size++;
    }

    public int indexOf(Object elemente) {
        for (int i = 0; i < size; i++) {
            if (elemente == elementData[i]) {
                return i;
            }
        }
        return -1;
    }

    //在obj前添加element
    public void addBefore(Object obj, Object element) {
        for (int i = 0; i < size; i++) {
            if(elementData[i]==obj) {
                add(i,element);
                return;
            }
        }
    }

    public void addAfter(Object obj, Object element) {
        for (int i = 0; i < size; i++) {
            if(elementData[i]==obj) {
                add(i+1,element);
                return;
            }
        }
    }

    public Object replace(int index, Object element) {
        elementData[index] = element;
        return element;
    }
}






















